#include "serialmaster.h"
#include <QDebug>

SerialMaster::SerialMaster(QObject *parent) : QObject(parent)
{
    setParent(parent);
    isConnected = false;
    isRxOn = false;
    slaveAddr = 0x00;

    timer = new QTimer(this);
    serial = new QSerialPort(this);
    serial->setBaudRate(QSerialPort::Baud9600);
    serial->setDataBits(QSerialPort::Data8);
    serial->setStopBits(QSerialPort::OneStop);
    serial->setParity(QSerialPort::NoParity);
    serial->setFlowControl(QSerialPort::NoFlowControl);

    connect(timer, SIGNAL(timeout()), this, SLOT(onRxTimeout()));
    connect(serial, SIGNAL(readyRead()), this, SLOT(receive()));
}

SerialMaster::~SerialMaster()
{
    delete serial;
}

QList<SerialMaster::Info> SerialMaster::availablePorts()
{
    QList<SerialMaster::Info> infos;
    QList<QSerialPortInfo> portInfos;

    portInfos = QSerialPortInfo::availablePorts();
    for(int i = 0; i < portInfos.size(); i++)
    {
        const QSerialPortInfo portInfo = portInfos.at(i);
        SerialMaster::Info info(portInfo.portName(), portInfo.isBusy());
        infos.append(info);
    }

    qDebug() << "Serial Num: " << infos.size();
    return infos;
}

enum SerialMaster::State SerialMaster::serialConnect(QString portName)
{
    if(portName.isEmpty())
    {
        return SerialMaster::State_Fail;
    }

    serial->setPortName(portName);
    bool connected = serial->open(QSerialPort::ReadWrite);
    if(connected != isConnected)
    {
        isConnected = connected;
        emit connectionChanged(isConnected);
    }

    return isConnected ? SerialMaster::State_Success : SerialMaster::State_Fail;
}

void SerialMaster::serialDisconnect()
{
    if(serial->isOpen())
    {
        serial->close();
        isConnected = false;
        emit connectionChanged(isConnected);
    }
}

QByteArray SerialMaster::calcChecksum(QByteArray data)
{

}

void SerialMaster::receive()
{
    if(! isRxOn)
    {
        serial->clear();
        return;
    }

    QByteArray in = serial->readAll();
    for(int i = 0; i < in.size(); i++)
    {
        quint8 b = in.at(i);
        int index = rxData.size();
        switch (index)
        {
        case 0:
            if(b == 0xff)
            {
                rxData.append(b);
            }
            break;

        case 1:
            if(b == slaveAddr)
            {
                rxData.append(b);
            }
            else
            {
                rxData.clear();
            }
            break;

        case 2:
            rxData.append(b);
            break;

        default:
            break;
        }
    }
}

void SerialMaster::onRxTimeout()
{

}
